package com.weixin.sdk.pay;

import java.util.Iterator;
import java.util.Map;
import java.util.Set;
import java.util.UUID;

import org.apache.log4j.Logger;
import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.DocumentHelper;
import org.dom4j.Element;

import com.weixin.sdk.kit.HttpKit;

public abstract class PayApi {
	protected abstract String getApiUrl();
	  public Logger logger = Logger.getLogger(getClass());
	  public BaseResData post(BaseReq reqData, byte[] certs)
	    throws Exception
	  {
	    String resultXml = HttpKit.post(getApiUrl(), getRequestXml(reqData.toMap()));
	    return getRespone(getResponseRoot(resultXml));
	  }
	  
	  public BaseResData post(BaseReq reqData)
	    throws Exception
	  {
	    String resultXml = HttpKit.post(getApiUrl(), getRequestXml(reqData.toMap()));
	    logger.info("resultXml:"+resultXml);
	    return getRespone(getResponseRoot(resultXml));
	  }
	  
	  protected String getRequestXml(Map<String, Object> parameters)
	  {
	    StringBuffer sb = new StringBuffer();
	    sb.append("<xml>");
	    Set<Map.Entry<String, Object>> es = parameters.entrySet();
	    Iterator<Map.Entry<String, Object>> it = es.iterator();
	    while (it.hasNext())
	    {
	      Map.Entry entry = (Map.Entry)it.next();
	      String k = (String)entry.getKey();
	      String v = (String)entry.getValue();
	      if (("attach".equalsIgnoreCase(k)) || ("body".equalsIgnoreCase(k)) || ("sign".equalsIgnoreCase(k))) {
	        sb.append("<" + k + ">" + "<![CDATA[" + v + "]]></" + k + ">");
	      } else {
	        sb.append("<" + k + ">" + v + "</" + k + ">");
	      }
	    }
	    sb.append("</xml>");
	    logger.info("getRequestXml:"+sb.toString());
	    return sb.toString();
	  }
	  
	  protected Element getResponseRoot(String responseXml)
	    throws DocumentException
	  {
	    Document root = DocumentHelper.parseText(responseXml);
	    return root.getRootElement();
	  }
	  
	  protected abstract BaseResData getRespone(Element paramElement);
	  
	  protected synchronized String getUUID()
	  {
	    return UUID.randomUUID().toString();
	  }

}
